import 'dart:convert';

import 'package:flutter/material.dart';
import 'package:multi_clickable_shape_widget/widget/LineBean.dart';
import 'package:multi_clickable_shape_widget/widget/common_util.dart';

class MultiClickableShapeController extends ChangeNotifier {
  MultiClickableShapeController(this._isEdit) {
    if (!isEdit) {
      if (params == null) {
        print("非编辑模式请设置参数");
      }
    }
  }
  List<PathBean> _lines = [];
  var _radius = 5.0;
  bool _isEdit = true;
  var _selectPathIndex = 0;
  int _selectDot = 0;
  var _width = 200.0;
  var _height = 200.0;
  Color _bgColor = Colors.grey;
  get width => _width;
  set width(v) {
    _width = v;
    notifyListeners();
  }

  Params? params;

  List<Offset> get currentLine => lines[_selectPathIndex].line;

  set height(v) {
    _height = v;
    notifyListeners();
  }

  get height => _height;
  bool get isEdit => _isEdit;

  double get radius => _radius;

  int get selectPathIndex => _selectPathIndex;

  int get selectDot => _selectDot;

  set selectDot(int selectDot) {
    _selectDot = selectDot;
    notifyListeners();
  }

  set selectPathIndex(int selectPathIndex) {
    _selectPathIndex = selectPathIndex;
    notifyListeners();
  }

  set isEdit(a) {
    _isEdit = a;
    notifyListeners();
  }

  void addLine(PathBean bean) {
    _lines.add(bean);
    _selectPathIndex = _lines.length - 1;
    notifyListeners();
  }

  void changeLineColorForIndex(int index, Color color) {
    _lines[index].color = color;
    notifyListeners();
  }

  void changeLine(int dragLine, lineIndex, offset) {
    _lines[dragLine].line[lineIndex] = offset;
    notifyListeners();
  }

  void changeAllLine(int pathIndex, DragUpdateDetails details) {
    _lines[pathIndex].line = _lines[pathIndex].line
        .map((m) => Offset(m.dx + details.delta.dx, m.dy + details.delta.dy))
        .toList();
    notifyListeners();
  }

  set currentX(x) {
    _lines[_selectPathIndex].line[_selectDot] = Offset(
      x,
      _lines[_selectPathIndex].line[_selectDot].dy,
    );
    notifyListeners();
  }

  set currentY(y) {
    _lines[_selectPathIndex].line[_selectDot] = Offset(
      _lines[_selectPathIndex].line[_selectDot].dx,
      y,
    );
    notifyListeners();
  }

  void setSelectDot(int index) {
    _selectDot = index;
    notifyListeners();
  }

  void removeCurrentDot() {
    try {
      _lines[_selectPathIndex].line.removeAt(_selectDot);
      _selectDot = _lines[_selectPathIndex].line.length - 1;
    } catch (e) {}
    notifyListeners();
  }

  void removePath() {
    _lines.removeAt(_selectPathIndex);
    _selectPathIndex = _lines.length - 1;
    notifyListeners();
  }

  void addDot(Offset offset) {
    if (_lines.isEmpty) {
      return;
    }
    _lines[_selectPathIndex].line.add(offset);
    notifyListeners();
  }

  void setColor(Color color) {
    _lines[_selectPathIndex].color = color;
    notifyListeners();
  }

  void changeMinusW() {
    _width = _width - 1;
    notifyListeners();
  }

  void changePlusW() {
    _width = _width + 1;
    notifyListeners();
  }

  void changeMinusH() {
    _height = _height - 1;
    notifyListeners();
  }

  void changePlusH() {
    _height = _height + 1;
    notifyListeners();
  }

  void setBgColor(Color color) {
    _bgColor = color;
    notifyListeners();
  }

  void moveToLast() {
    moveElementToLast(_lines, _lines[_selectPathIndex]);
    notifyListeners();
  }

  void moveToBackward() {
    moveElementBackward(_lines, _lines[_selectPathIndex]);
    notifyListeners();
  }

  String get getParams {
    return jsonEncode(
      Params(
        lines: _lines,
        radius: radius,
        width: _width,
        height: _height,
        bgColor: _bgColor,
      ).toJson(),
    );
  }

  List<PathBean> get lines => _lines;

  Color get bgColor => _bgColor;

  Offset get currentDot => lines[_selectPathIndex].line[_selectDot];
  PathBean get currentPath => lines[_selectPathIndex];

  set setParams(String jsonText) {
    params = Params.fromJson(jsonDecode(jsonText));
    if (params == null) {
      return;
    }
    _height = params!.height;
    _width = params!.width;
    _radius = params!.radius;
    _lines = params!.lines;
    _bgColor = params!.bgColor;
    notifyListeners();
  }
}

class Params {
  final List<PathBean> lines;
  final double radius;
  final double width;
  final double height;
  final Color bgColor;

  Params({
    required this.lines,
    required this.radius,
    required this.width,
    required this.height,
    required this.bgColor,
  });
  Map<String, dynamic> toJson() {
    return {
      "lines": lines.map((m) => m.toJson()).toList(),
      "radius": radius,
      "width": width,
      "height": height,
      "bgColor": bgColor.value,
    };
  }

  factory Params.fromJson(Map<String, dynamic> json) {
    return Params(
      lines: (json['lines'] as List)
          .map((e) => PathBean.fromJson(e as Map<String, dynamic>))
          .toList(),
      radius: json['radius'],
      width: json['width'],
      height: json['height'],
      bgColor: Color(json['bgColor']),
    );
  }
}
